package main

import "fmt"

type User struct {
	id   int
	name string
	age  int
}

func test01(p0 User) {
	p0.name = "lucy"
	fmt.Println("test01:", p0)
}

func test02(p1 *User) {
	p1.name = "Lily"
	fmt.Println("test02:", *p1)
}

//结构体
func main() {
	//顺序初始化，每个成员变量都必须初始化
	var u1 User = User{1, "tom", 20}
	fmt.Println("u1=", u1)
	//指定成员初始化，没有初始化的自动赋类型初始值
	var u2 User = User{name: "lily"}
	fmt.Println("u2=", u2)
	//指针变量初始化
	p1 := &User{2, "max", 25}
	fmt.Println("p1=", *p1)
	//操作成员变量，需要用.
	var u3 User
	u3.id = 4
	u3.name = "bob"
	u3.age = 30
	fmt.Println("u3=", u3)

	//指针有合法指向可以操作成员
	var u4 User
	p4 := &u4
	p4.id = 4
	p4.name = "snow"
	p4.age = 28
	fmt.Println("p4=", p4)

	var u40 User
	u40.id = 4
	u40.name = "snow"
	u40.age = 28
	fmt.Println("u4=u40", u4 == u40)
	//用new可以初始化，返回地址
	var u5 = new(User)
	u5.id = 5
	u5.name = "mike"
	u5.age = 23
	fmt.Println("p4=", u5)

	//结构体比较 == 或 !=
	var u6 = new(User)
	u6.id = 5
	u6.name = "mike"
	u6.age = 23
	fmt.Println("u5==u6", u5 == u6) //比较的结构体地址
	u7 := u6
	fmt.Println("u6==u7", u6 == u7)

	//结构体参数，不用拷贝传递，一般用地址传递
	test01(u4) //拷贝传递
	fmt.Println("u4=", u4)
	test02(u7) //new 返回的是地址，所以可以作地址传递
	fmt.Println("u7=", *u7)

	//可见性： 首字母是大写就是public ， 首字母小字只能在同一个包里使用protected

}
